

Creep.prototype.registerTowerCarryInRoom=function () {
    let room = Game.rooms[this.memory["roomName"]]
    room.used = room.used||{}
    let id = this.headTask().id;
    room.used[id] = (room.used[id] || 0)+this.getPartCnt(CARRY)*50
};


let pro={
    stationName:"stationTower",
    needRepairsRoomMap:{},
    towerRepairMap:{},
    lastUpdateMap:{},
    lastActiveMap:{},
    update:function (room) {
        pro.lastUpdateMap[room.name] = (pro.lastUpdateMap[room.name] || 0) - 1;

        let roadNeedRepair = undefined
        if(room.memory.structMap&&room.memory.structMap[STRUCTURE_ROAD]){ // 如果有缓存路只修要缓存的路
            let roadPos = Utils.decodePosArray(room.memory.structMap[STRUCTURE_ROAD])
            roadNeedRepair = {}
            roadPos.forEach(e=>roadNeedRepair[e.x*50+e.y] = 1)
        }

        // 记录要修理的 东西
        pro.needRepairsRoomMap[room.name] = room.find(FIND_STRUCTURES)
            .filter(e => e.structureType != STRUCTURE_WALL && e.structureType != STRUCTURE_RAMPART)
            .filter(e => e.hits / e.hitsMax < 0.8 && e.hits < 10000000)
            .filter(e => (!roadNeedRepair||roadNeedRepair[e.pos.x*50+e.pos.y])||e.structureType != STRUCTURE_ROAD)
            .sort((a, b) => a.hits - b.hitsMax)
            .map(e => e.id)
    },
    exec:function (room){
        if (!pro.lastUpdateMap[room.name]||pro.lastUpdateMap[room.name] <= 0) {
            pro.lastUpdateMap[room.name] = 10
            let hostiles = room.find(FIND_HOSTILE_CREEPS);
            let randomAttack = undefined;
            if(hostiles.length){
                let randomAttack = Utils.randomGet(hostiles);
                pro.lastUpdateMap[room.name] = 0;
                hostiles = hostiles.sort((a,b)=>a.hits/a.hitsMax!=b.hits/b.hitsMax?(a.hits/a.hitsMax-b.hits/b.hitsMax):a.hits-b.hits)
            }

            room.tower.forEach(tower => {
                if(hostiles.length){
                    let headHostiles = hostiles.head()
                    if(headHostiles.hits!=headHostiles.hitsMax){
                        tower.attack(headHostiles)
                    }else{
                        if(Game.time%10==0){
                            tower.attack(randomAttack)
                        }else if(Game.time%10==4){
                            randomAttack = Utils.randomGet(hostiles);
                            tower.attack(randomAttack)
                        }
                    }
                    return;
                }

                // let inner = pos => pos.x >= 2 && pos.x <= 47 && pos.y >= 2 && pos.y <= 47;
                // if (closestHostile && (inner(closestHostile.pos))) {
                //     tower.attack(closestHostile);
                //     pro.lastUpdateMap[room.name]=0
                //     return;
                // }

                let closestMyCreeps = tower.pos.findClosestByRange(FIND_MY_CREEPS,{filter:e=>e.hits!=e.hitsMax});
                if(closestMyCreeps){
                    tower.heal(closestMyCreeps)
                    pro.lastUpdateMap[room.name]=0
                    return;
                }

                if (!pro.needRepairsRoomMap[room.name]) pro.needRepairsRoomMap[room.name] =[]
                let id = this.towerRepairMap[tower.id] = this.towerRepairMap[tower.id] || pro.needRepairsRoomMap[room.name].shift();
                let target = Game.getObjectById(id)
                if (!target||target.hits / target.hitsMax > 0.9) {
                    id = this.towerRepairMap[tower.id] = pro.needRepairsRoomMap[room.name].shift();
                    target = Game.getObjectById(id)
                }
                if(target){
                    tower.repair(target)
                    // HelperVisual.commonText(tower.room.name,target.hits/target.hitsMax,target)
                    pro.lastUpdateMap[room.name]=0
                }
            })
        }
        pro.lastUpdateMap[room.name] -= 1
    },
    generatorFillEnergyTasks:function(roomName){
        let room = Game.rooms[roomName.name||roomName]
        return room.tower.filter(e=>e.store[RESOURCE_ENERGY]+(room.used&&room.used[e.id]||0)<=600).map(e=>
            [UtilsTask.task(e,"fillRes","registerTowerCarryInRoom",{resType:RESOURCE_ENERGY})]
        )
    }


};



global.StationTower=pro;